/**
 * Items panel - jQuery EasyUI Extension
 * 
 * Copyright (c) 2009-2013 Rime Lee. All rights reserved.
 * 
 * Accepted JSON object: Array of ItemNode.
 * 
 * ItemNode format:
 * {"id":"1","name":"tom","brief":"hello","iconCls":"icon-xyz","attributes":{"attr1":"abc","attr2":"123"}}
 */
(function($) {
	$.fn.smartpanel = function(options, param) {
		if (typeof options == 'string') {
			return $.fn.smartpanel.methods[options](this, param);
		}

		options = options || {};
		return this.each(function() {
			var target = this;
			var state = $.data(target, 'smartpanel');
			if (state) {
				$.extend(state.options, options);
			} else {
				state = {
					options : $.extend({}, $.fn.smartpanel.defaults, options, {
						loadData : function(data) {
							loadData(this, data);
						}
					})
				};
				$.data(target, 'smartpanel', state);
				create(target, state);
			}
			if (state.options.data) {
				loadData(target, state.options.data);
			} else {
				$.jsonloader(target, state.options);
			}
		});
	};

	function create(target, state) {
		$(target).addClass('smartpanel-panel');
		if (state.options.menu) {
			var menuData = state.options.menu;
			state.menu = $('<div></div>').appendTo(target).menu({
				onClick : function(item) {
					for (var i = 0; i < menuData.length; i++) {
						if (item.id == ('M_' + i)) {
							if (menuData[i].onClick) {
								var d = $.data(item.target, 'smartpanel-menu');
								menuData[i].onClick.call(target, d);
							}
							break;
						}
					}
				}
			});
		}
	}

	function getPanel(target) {
		return $(target);
	}

	/**
	 * load data, the old items will be removed.
	 */
	function loadData(target, data) {
		var opts = $.data(target, 'smartpanel').options;
		$.data(target, 'smartpanel').data = data;
		var panel = getPanel(target);
		panel.empty();
		for (var i = 0; i < data.length; i++) {
			if (opts.filter.call(target, data[i]) != false) {
				createItem(target, panel, opts, data[i]);
			}
		}
	}

	function createItem(target, panel, opts, itemData) {
		var item = $('<div class="smartpanel-item"></div>').appendTo(panel);
		var item_data = $.extend({
			target : item[0]
		}, itemData);
		$.data(item[0], "smartpanel-item", item_data);
		formatter(item, item_data);
		bindEvent(target, opts, item, item_data);
		return item;
	}

	function formatter(item, item_data) {
		var _html = "<table border='0' cellspacing='0' cellpadding='0' class='smartpanel-item-box'><tr>";
		_html += "<th rowspan='2' class='smartpanel-item-icon'>";
		if (item_data.iconCls) {
			_html += ("<div class='smartpanel-item-icon " + item_data.iconCls + "'></div>");
		}
		_html += "</th>";
		_html += "<td class='smartpanel-item-name'></td></tr>";
		_html += "<tr><td class='smartpanel-item-brief'></td></tr></table>";
		var box = $(_html).appendTo(item);
		if (item_data.name) {
			$('td.smartpanel-item-name', box).html(item_data.name);
		}
		if (item_data.brief) {
			$('td.smartpanel-item-brief', box).html(item_data.brief);
		}
	}

	function bindEvent(target, opts, item, itemData) {
		item.hover(function() {
			$(this).addClass('smartpanel-item-hover');
		}, function() {
			$(this).removeClass('smartpanel-item-hover');
		}).dblclick(itemData, function(e) {
			if (opts.onDblClick) {
				opts.onDblClick.call(target, e.data);
			}
		});
		if (opts.menu) {
			item.bind('contextmenu', itemData, function(e) {
				var menu = buildMenu(target, e.data);
				menu.find('div.menu-item').each(function() {
					$.data(this, 'smartpanel-menu', e.data);
				});
				e.preventDefault();
				menu.menu('show', {
					left : e.pageX,
					top : e.pageY
				});
			});
		}
	}

	function buildMenu(target, itemData) {
		var state = $.data(target, 'smartpanel');
		var mm = state.menu;
		if (state.options.menu && mm) {
			mm.empty();
			for (var i = 0; i < state.options.menu.length; i++) {
				var menu_item = state.options.menu[i];
				if (menu_item.onBeforeShow) {
					if (menu_item.onBeforeShow.call(target, itemData) == false) {
						continue;
					}
				}
				mm.menu('appendItem', {
					id : 'M_' + i,
					text : menu_item.text,
					iconCls : menu_item.iconCls
				});
			}
		}
		return mm;
	}

	function appendItem(target, itemData) {
		var opts = $.data(target, 'smartpanel').options;
		if (opts.filter.call(target, itemData) != false) {
			var data = $.data(target, 'smartpanel').data;
			data.push(itemData);
			var panel = getPanel(target);
			createItem(target, panel, opts, itemData);
		}
	}

	function removeItem(target, itemEl) {
		var itemData = $.data(itemEl, 'smartpanel-item');
		var data = $.data(target, 'smartpanel').data;
		for (var i = 0; i < data.length; i++) {
			if (itemData.id == data[i].id) {
				data.splice(i, 1);
				break;
			}
		}
		$.removeData(itemEl, "smartpanel-item");
		$(itemEl).unbind();
		$(itemEl).remove();
	}

	$.fn.smartpanel.methods = {
		options : function(jq) {
			return $.data(jq[0], 'smartpanel').options;
		},
		getData : function(jq) {
			return $.data(jq[0], 'smartpanel').data;
		},
		load : function(jq, data) {
			return jq.each(function() {
				loadData(this, data);
			});
		},
		reload : function(jq, param) {
			return jq.each(function() {
				var opts = $.data(jq[0], 'smartpanel').options;
				if (param) {
					opts.queryParams = param;
				}
				$.jsonloader(this, opts);
			});
		},
		/**
		 * append grid item, the param contains following properties:
		 * id,name,brief,iconCls,attributes
		 */
		appendItem : function(jq, param) {
			return jq.each(function() {
				appendItem(this, param);
			});
		},
		removeItem : function(jq, itemEl) {
			return jq.each(function() {
				removeItem(this, itemEl);
			});
		}
	};

	$.fn.smartpanel.defaults = $.extend({}, $.jsonloader.defaults, {
		data : null,
		menu : null,
		filter : function(item) {
			return true;
		},
		onDblClick : function(item) {
		}
	});

	var cssloaded = false;
	if (window.jQuery) {
		jQuery(function() {
			if (!cssloaded) {
				easyloader.load('extends/smartpanel.css', function() {
					cssloaded = true;
				});
			}
		});
	}
})(jQuery);